package it.polito.connectedcar.message;

import it.polito.connectedcar.tcc.TCCVehicleAbstraction;
import it.polito.connectedcar.tcc.zone.ZoneToken;
import it.polito.connectedcar.util.Constants;
import it.polito.connectedcar.vehicle.SUMOVehicleToken;

/**
 * This message is used by the TCC to extract information coming from vehicles.
 * Different actionCodes exist for a vehicle communicating with a TCC.
 * <ul>
 * <li>
 * -<b>VEHICLE_UPDATE_MESSAGE_CODE</b> : the vehicle is sending a normal update
 * message containing its position,speed,direction,id and belonging Token.
 * 
 * </li>
 * <br/>
 * <li>
 * -<b>VEHICLE_GOODBYE_MESSAGE_CODE</b> : the vehicle is leaving the token
 * possibly managed by the receiving TCC and has to send a message containing
 * the old and the new token-</li>
 * </ul>
 * 
 * @author Nicola Aresta
 * 
 */
public class TCCFromVehicleMessage extends IncomingMessage {

	private TCCVehicleAbstraction tccVehicleAbstraction;
	private boolean isVehicleUpdate;
	private boolean isvehicleGoodBye;

	public TCCFromVehicleMessage(byte[] data) {
		super(data, Constants.VEHICLE_TYPE_CODE);
	}

	@Override
	protected boolean onProcessMessage(Storage st) {

		switch (actionCode) {
			case Constants.VEHICLE_UPDATE_MESSAGE_CODE :
				setVehicleUpdate(true);
				tccVehicleAbstraction = new TCCVehicleAbstraction();
				byte[] bel_token = new byte[TOKEN_LENGTH];
				byte[] app_token = new byte[TOKEN_LENGTH];

				for (int i = 0; i < TOKEN_LENGTH; i++)
					bel_token[i] = (byte) st.readByte();

				for (int i = 0; i < TOKEN_LENGTH; i++)
					app_token[i] = (byte) st.readByte();

				ZoneToken belongingToken = new ZoneToken(bel_token);
				ZoneToken approachingToken = new ZoneToken(app_token);
				tccVehicleAbstraction.setBelongingToken(belongingToken);
				tccVehicleAbstraction.setApproachingToken(approachingToken);
				tccVehicleAbstraction.setAddress(getSourceAddress());
				tccVehicleAbstraction.setVehicleId(new SUMOVehicleToken(st.readStringASCII()));
				tccVehicleAbstraction.setUtmXPos(st.readDouble());
				tccVehicleAbstraction.setUtmYPos(st.readDouble());
				tccVehicleAbstraction.setCurrentDirection(st.readDouble());
				tccVehicleAbstraction.setSpeed(st.readDouble());
				tccVehicleAbstraction.setCurrentLaneId(st.readStringASCII());
				break;
			case Constants.VEHICLE_GOODBYE_MESSAGE_CODE :

				setIsvehicleGoodBye(true);
				bel_token = new byte[TOKEN_LENGTH];
				app_token = new byte[TOKEN_LENGTH];

				for (int i = 0; i < TOKEN_LENGTH; i++)
					bel_token[i] = (byte) st.readByte();

				for (int i = 0; i < TOKEN_LENGTH; i++)
					app_token[i] = (byte) st.readByte();

				ZoneToken oldToken = new ZoneToken(bel_token);
				ZoneToken newToken = new ZoneToken(app_token);
				tccVehicleAbstraction = new TCCVehicleAbstraction();
				tccVehicleAbstraction.setBelongingToken(oldToken);
				tccVehicleAbstraction.setApproachingToken(newToken);
				tccVehicleAbstraction.setVehicleId(new SUMOVehicleToken(st
						.readStringASCII()));
				tccVehicleAbstraction.setAddress(getSourceAddress());
				break;
			default :
				return false;
		}

		return true;
	}

	@Override
	protected void convertFromData(Storage st) {
		// TODO not implemented

	}

	public boolean isVehicleUpdate() {
		return isVehicleUpdate;
	}

	public void setVehicleUpdate(boolean isVehicleUpdate) {
		this.isVehicleUpdate = isVehicleUpdate;
	}

	public boolean isIsVehicleGoodBye() {
		return isvehicleGoodBye;
	}

	public void setIsvehicleGoodBye(boolean isvehicleGoodBye) {
		this.isvehicleGoodBye = isvehicleGoodBye;
	}

	public TCCVehicleAbstraction getTccVehicleAbstraction() {
		return tccVehicleAbstraction;
	}

	public void setTccVehicleAbstraction(TCCVehicleAbstraction tccVehicleAbstraction) {
		this.tccVehicleAbstraction = tccVehicleAbstraction;
	}

}
